package com.naiterui.common.jinshuju.util;

import static org.springframework.http.MediaType.ALL;
import static org.springframework.http.MediaType.APPLICATION_JSON_UTF8;
import static org.springframework.http.MediaType.TEXT_HTML;
import static org.springframework.http.MediaType.TEXT_PLAIN;

import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.text.SimpleDateFormat;
import java.util.List;
import java.util.TimeZone;

import org.springframework.http.HttpStatus;
import org.springframework.http.client.ClientHttpResponse;
import org.springframework.http.client.SimpleClientHttpRequestFactory;
import org.springframework.http.converter.ByteArrayHttpMessageConverter;
import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.http.converter.StringHttpMessageConverter;
import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter;
import org.springframework.http.converter.support.AllEncompassingFormHttpMessageConverter;
import org.springframework.web.client.DefaultResponseErrorHandler;
import org.springframework.web.client.RestTemplate;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import com.google.common.base.Charsets;
import com.google.common.collect.Lists;

/**
 * 创建RestTemplate工具类
 */
public class RestTemplateUtil {
    public static final Integer DEFAULT_CONNECT_TIMEOUT = 5000;
    public static final Integer DEFAULT_READ_TIMEOUT = 5000;
    public static final Integer DEFAULT_CONNECTION_REQUEST_TIME_OUT = 5000;

    private RestTemplateUtil() {
    }

    public static RestTemplate create() {
        return RestTemplateUtil.create(DEFAULT_CONNECT_TIMEOUT, DEFAULT_READ_TIMEOUT);
    }

    public static RestTemplate create(int connectTimeout, int readTimeout) {
        List<HttpMessageConverter<?>> converterList = Lists.newArrayList();
        //设置UTF-8 默认是ISO_8859_1
        StringHttpMessageConverter stringHttpMessageConverter = new StringHttpMessageConverter(StandardCharsets.UTF_8);
        stringHttpMessageConverter.setSupportedMediaTypes(Lists.newArrayList(ALL));
        converterList.add(stringHttpMessageConverter);
        //如果不设置AllEncompassingFormHttpMessageConverter，那么访问其他服务将会获取不到参数application/x-www-form-urlencoded, multipart/form-data
        converterList.add(new AllEncompassingFormHttpMessageConverter());
        converterList.add(RestTemplateUtil.mappingJacksonHttpMessageConverter());
        converterList.add(new ByteArrayHttpMessageConverter());
        SimpleClientHttpRequestFactory requestFactory = new SimpleClientHttpRequestFactory();
        requestFactory.setConnectTimeout(connectTimeout);
        requestFactory.setReadTimeout(readTimeout);
        RestTemplate restTemplate = new RestTemplate(requestFactory);
        restTemplate.setMessageConverters(converterList);
        restTemplate.setErrorHandler(new DefaultResponseErrorHandler() {
            @Override
            public boolean hasError(ClientHttpResponse response) throws IOException {
                HttpStatus statusCode = HttpStatus.resolve(response.getRawStatusCode());
                if (statusCode == HttpStatus.BAD_REQUEST) {
                    return false;
                }
                return super.hasError(response);
            }
        });
        return restTemplate;
    }

    public static MappingJackson2HttpMessageConverter mappingJacksonHttpMessageConverter() {
        MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter();
        //设置日期格式
        ObjectMapper objectMapper = new ObjectMapper();
        //正八区
        objectMapper.setTimeZone(TimeZone.getTimeZone("GMT+8"));
        objectMapper.setDateFormat(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"));
        objectMapper.registerModule(new JavaTimeModule());
        converter.setObjectMapper(objectMapper);
        converter.setSupportedMediaTypes(Lists.newArrayList(APPLICATION_JSON_UTF8, TEXT_HTML, TEXT_PLAIN));
        converter.setDefaultCharset(Charsets.UTF_8);
        return converter;
    }
}
